<template>
  <div class="ie-editor" style="width: 100%;">
    <div v-if="loading" style="position: relative; height: 120px; text-align: center;">
      <n-spin size="medium" />
    </div>
    <textarea style="opacity: 0;" ref="editorRef"></textarea>
  </div>
</template>

<script setup>
import { ref, watch, onMounted, onBeforeUnmount } from 'vue'
import { toPng } from 'html-to-image'
import { useApi } from '/@/api'
import zhCN from '/@/assets/tinymce/i18n/zh_CN.json'

window.$toPng = toPng

const props = defineProps({
  value: {
    type: String,
    default: ''
  }
})

const loading = ref(true)
const editorRef = ref()
const editorInstance = ref()

function setContent(s) {
  if (
    typeof s === 'string' &&
    editorInstance.value?.setContent
  ) {
    editorInstance.value.setContent(s)
  }
}

function getContent() {
  if (editorInstance.value?.getContent) {
    return editorInstance.value.getContent()
  }
}

defineExpose({ setContent, getContent })

onMounted(() => {
  if (window.tinymce) {
    if (!window.tinymce.i18n.hasCode('zh_CN')) {
      window.tinymce.addI18n('zh_CN', zhCN)
    }

    window.tinymce
      .init({
        language: 'zh_CN',
        // selector: '#editor',
        target: editorRef.value,
        branding: false,
        plugins: 'print preview paste importcss searchreplace autolink directionality code visualblocks visualchars fullscreen image link media codesample table charmap hr pagebreak nonbreaking anchor toc insertdatetime advlist lists wordcount imagetools textpattern noneditable help charmap quickbars emoticons katex',
        // imagetools_cors_hosts: ['picsum.photos'],
        images_upload_handler(blobInfo, success, failure) {
          const formData = new FormData()

          formData.append('file',
            blobInfo.blob(),
            blobInfo.filename()
          )

          useApi()
            .upload('upload', formData, { prefixUrl: '/api' })
            .then(res => {
              if (res.code === 0) {
                return success(res.data?.filepath)
              }

              failure(res.message)
            })
        },
        menubar: 'file edit view insert format tools table help',
        toolbar: 'undo redo | bold italic underline strikethrough | fontselect fontsizeselect formatselect | alignleft aligncenter alignright alignjustify | outdent indent | numlist bullist | forecolor backcolor removeformat | pagebreak | charmap emoticons katex | fullscreen preview print | insertfile image media link anchor codesample | ltr rtl',
        toolbar_sticky: true,
        image_advtab: true,
        // image data-mce-src
        importcss_append: true,
        relative_urls: false,
        remove_script_host: true,
        height: 600,
        image_caption: true,
        quickbars_selection_toolbar: 'bold italic | quicklink h2 h3 blockquote quickimage quicktable',
        noneditable_noneditable_class: 'mceNonEditable',
        toolbar_mode: 'sliding',
        contextmenu: 'link image imagetools table',
        skin: 'oxide',
        content_css: 'default,/static/katex/katex.min.css',
        content_style: '',
        valid_elements: '*[*]',
        valid_children: '*[*]',
        font_formats: [
          'Andale Mono=andale mono,times',
          'Arial=arial,helvetica,sans-serif',
          'Arial Black=arial black,avant garde',
          'Book Antiqua=book antiqua,palatino',
          'Comic Sans MS=comic sans ms,sans-serif',
          'Courier New=courier new,courier',
          'Georgia=georgia,palatino',
          'Helvetica=helvetica',
          'Impact=impact,chicago',
          'Oswald=oswald',
          'Symbol=symbol',
          'Tahoma=tahoma,arial,helvetica,sans-serif',
          'Terminal=terminal,monaco',
          'Times New Roman=times new roman,times',
          'Trebuchet MS=trebuchet ms,geneva',
          'Verdana=verdana,geneva',
          'Webdings=webdings',
          'Wingdings=wingdings,zapf dingbats',
          // '宋体=SimSun,sans-serif',
          // '楷体=KaiTi,sans-serif',
          // '微软雅黑=Microsoft YaHei,sans-serif'
        ].join('; '),
        init_instance_callback(editor) {
          loading.value = false
          editorInstance.value = editor

          watch(
            () => props.value,
            setContent, {
              immediate: true
            }
          )
        }
      })
  }
})

onBeforeUnmount(() => {
  if (editorInstance.value) {
    window.tinymce.remove(editorInstance.value)
  }
})
</script>